<!--
 * @Author: 傅湘乐 fuxiangle@dhcc.com.cn
 * @Date: 2023-02-16 11:24:44
 * @LastEditors: 傅湘乐 fuxiangle@dhcc.com.cn
 * @LastEditTime: 2023-02-17 11:59:17
 * @FilePath: \sloth-admin-vue3-vite3\src\views\assembly\fileView\index.vue
 * @Description: 这是默认设置,请设置`customMade`, 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
-->
<template>
	<div class="card">
		<h1>ppt,pdf,excel,word文件预览组件</h1>
		<el-row :gutter="40">
			<el-col :span="7">
				<div class="mar_b30">
					<input type="file" ref="xlsRef" accept=".xls,.xlsx" />
					<button @click="handleExcelView">点击预览excel文件</button>
				</div>
				<div class="mar_b30">
					<input type="file" ref="docRef" accept=".docx" />
					<button @click="handleDoclView">点击预览doc文件</button>
				</div>
				<div class="mar_b30">
					<el-link type="primary" @click="onlineViewClick(0)">点击预览PDF文件</el-link>
				</div>
				<div>
					<el-link type="primary" @click="onlineViewClick(1)">点击预览PPTX文件</el-link>
				</div>
			</el-col>
			<el-col :span="17">
				<div v-html="excelData"></div>
				<div ref="bodyContainer"></div>
				<div id="pptx"></div>
			</el-col>
		</el-row>
	</div>
</template>

<script setup lang="ts" name="fileView">
import * as XLSX from 'xlsx'
import { ref, onMounted, getCurrentInstance } from 'vue'
import { renderAsync } from 'docx-preview'
const $ = (window as any).$
let refs = null
const xlsRef = ref()
const docRef = ref()
const bodyContainer = ref()
onMounted(() => {
	let { $refs } = (getCurrentInstance() as any).proxy
	// 你可以打印一下(getCurrentInstance() as any)会在 proxy 中发现 $refs
	refs = $refs
	xlsRef.value = refs.xlsRef // 使用refs获取dom
	docRef.value = refs.docRef
	bodyContainer.value = refs.bodyContainer
	console.log('确认JQuery成功引入:' + $)
})

// 获取到上传附件的事件
const docxOptions = {
	className: 'docxBox', // string：默认和文档样式类的类名/前缀
	inWrapper: true, // boolean：启用围绕文档内容的包装器渲染
	ignoreWidth: false, // boolean：禁用页面的渲染宽度
	ignoreHeight: false, // boolean：禁止渲染页面高度
	ignoreFonts: false, // boolean：禁用字体渲染
	breakPages: true, // boolean：在分页符上启用分页
	ignoreLastRenderedPageBreak: true, // boolean：在 lastRenderedPageBreak 元素上禁用分页
	experimental: false, // boolean：启用实验功能（制表符停止计算）
	trimXmlDeclaration: true, // boolean：如果为true，解析前会从​​ xml 文档中移除 xml 声明
	useBase64URL: false, // boolean：如果为true，图片、字体等会转为base 64 URL，否则使用URL.createObjectURL
	useMathMLPolyfill: false, // boolean：包括用于 chrome、edge 等的 MathML polyfill。
	showChanges: false, // boolean：启用文档更改的实验性渲染（插入/删除）
	debug: false // boolean：启用额外的日志记录
}
const handleDoclView = () => {
	let file = docRef.value.files[0]
	if (!file) return
	// 将file转为buffer
	let fr = new FileReader()
	fr.readAsArrayBuffer(file)
	fr.addEventListener(
		'loadend',
		e => {
			console.log('loadend---->', e)
			let buffer = e.target?.result
			renderAsync(
				buffer, // Blob | ArrayBuffer | Uint8Array, 可以是 JSZip.loadAsync 支持的任何类型
				bodyContainer.value, // HTMLElement 渲染文档内容的元素,
				null!, // HTMLElement, 用于呈现文档样式、数字、字体的元素。如果为 null，则将使用 bodyContainer。
				docxOptions // 配置
			).then((res: any) => {
				console.log('res---->', res)
			})
		},
		false
	)
}
//excel文件预览
const excelData = ref()
const handleExcelView = () => {
	let file = xlsRef.value.files[0]
	if (!file) return
	// 将file转为buffer
	let fr = new FileReader()
	fr.readAsArrayBuffer(file)
	fr.addEventListener(
		'loadend',
		e => {
			console.log('loadend---->', e)
			const data = new Uint8Array(e.target?.result as never)
			const workbook = XLSX.read(data, { type: 'array' })
			const sheetNames = workbook.SheetNames // 工作表名称集合
			const worksheet = workbook.Sheets[sheetNames[0]]
			// const excelData = XLSX.utils.sheet_to_json(worksheet) //最终解析xlsx格式的文件得出来的数据
			excelData.value = XLSX.utils.sheet_to_html(worksheet)
		},
		false
	)
}

//pdf文件预览
const onlineViewClick = (flag: number) => {
	if (flag == 0) {
		window.open('http://fe.dhcc.work/aaa/a.pdf', '_blank')
	} else {
		$('#pptx').children().remove() //删除所有子节点，防止重复点击造成的数据重复
		$('#pptx').pptxToHtml({
			pptxFileUrl: '/PPTXjs/a.pptx',
			slidesScale: '100%',
			slideMode: true, //true 工具栏显示 实现幻灯片播放形式
			keyBoardShortCut: false
		})
	}
}
</script>

<style scoped lang="scss">
.mar_b30 {
	margin-bottom: 30px;
}
.docxBox {
	background: #000000;
}
</style>
